<script setup lang='ts'>
import type { Ref } from 'vue'
import { computed, onMounted, ref } from 'vue'
import { useRoute } from 'vue-router'
import { NAutoComplete, NButton, NInput, useDialog } from 'naive-ui'
import { AzureKeyCredential, OpenAIClient } from '@azure/openai'
import { Message } from './components'
import { useScroll } from './hooks/useScroll'
import { useChat } from './hooks/useChat'
import { SvgIcon } from '@/components/common'
import { useChatStore } from '@/store'
import { t } from '@/locales'

const route = useRoute()
const dialog = useDialog()

const chatStore = useChatStore()

async function askHandler(msg: string) {
  const endpoint = 'https://swedencentral-aoai-test.openai.azure.com/'
  const azureApiKey = 'd860db0913144102bda5dd618f17f4c7'
  const message = [
    {
      role: 'user',
      content: msg,
    },
  ]
  const deploymentId = 'testGPT3'
  const client = new OpenAIClient(endpoint, new AzureKeyCredential(azureApiKey))
  const result = await client.getChatCompletions(deploymentId, message)
  return result?.choices[0]?.message?.content || ''
}

const { addChat } = useChat()
const { scrollRef, scrollToBottom } = useScroll()

const { uuid } = route.params as { uuid: string }

const dataSources = computed(() => chatStore.getChatByUuid(+uuid))

const prompt = ref<string>('')
const loading = ref<boolean>(false)
const inputRef = ref<Ref | null>(null)

async function handleSubmit() {
  const message = prompt.value

  if (loading.value)
    return

  if (!message || message.trim() === '')
    return

  loading.value = true
  prompt.value = ''

  addChat(
    +uuid,
    {
      dateTime: new Date().toLocaleString(),
      text: message,
      loading: false,
      isUser: true,
      error: false,
      conversationOptions: null,
      requestOptions: { prompt: message, options: null },
    },
  )
  const answer = await askHandler(message)

  loading.value = false

  addChat(
    +uuid,
    {
      dateTime: new Date().toLocaleString(),
      text: answer,
      isUser: false,
      error: false,
      conversationOptions: null,
      requestOptions: { prompt: message, options: null },
    },
  )
  scrollToBottom()
}

function handleClear() {
  if (loading.value)
    return

  dialog.warning({
    title: t('chat.clearChat'),
    content: t('chat.clearChatConfirm'),
    positiveText: t('common.yes'),
    negativeText: t('common.no'),
    onPositiveClick: () => {
      chatStore.clearChatByUuid(+uuid)
    },
  })
}

function handleEnter(event: KeyboardEvent) {
  if (event.key === 'Enter' && !event.shiftKey) {
    event.preventDefault()
    handleSubmit()
  }
}

const buttonDisabled = computed(() => {
  return loading.value || !prompt.value || prompt.value.trim() === ''
})

onMounted(() => {
  scrollToBottom()
  if (inputRef.value)
    inputRef.value?.focus()
})
</script>

<template>
  <div class="h-full w-full flex flex-col">
    <main class="flex-1 overflow-hidden">
      <div id="scrollRef" ref="scrollRef" class="h-full overflow-hidden overflow-y-auto">
        <div
          id="image-wrapper"
          class="m-auto w-full p-2 dark:bg-[#101014] md:p-4"
        >
          <template v-if="!dataSources.length">
            <div class="mt-4 flex items-center justify-center text-center text-neutral-300">
              <SvgIcon icon="ri:bubble-chart-fill" class="mr-2 text-3xl text-green-200" />
              <span>{{ t('chat.newChatTitle') }}</span>
            </div>
          </template>
          <template v-else>
            <div>
              <Message
                v-for="(item, index) of dataSources"
                :key="index"
                :date-time="item.dateTime"
                :text="item.text"
                :is-user="item.isUser"
                :error="item.error"
              />
              <div />
            </div>
          </template>
          <div v-if="loading" class="flex-center">
            <SvgIcon icon="svg-spinners:3-dots-fade" class="text-3xl" />
          </div>
        </div>
      </div>
    </main>

    <footer>
      <div class="m-auto w-full px-4 pb-4 md:px-10">
        <div class="flex items-center justify-between space-x-2">
          <span class="cursor-pointer rounded-full text-xl text-[#4f555e] dark:text-white hover:text-red" @click="handleClear">
            <SvgIcon icon="ri:delete-bin-line" />
          </span>
          <NAutoComplete v-model:value="prompt">
            <template #default="{ handleInput, handleBlur, handleFocus }">
              <NInput
                ref="inputRef"
                v-model:value="prompt"
                type="textarea"
                :placeholder="t('chat.placeholder')"
                :autosize="{ minRows: 1, maxRows: 8 }"
                @input="handleInput"
                @focus="handleFocus"
                @blur="handleBlur"
                @keypress="handleEnter"
              />
            </template>
          </NAutoComplete>
          <NButton type="primary" :disabled="buttonDisabled" @click="handleSubmit">
            <template #icon>
              <span class="dark:text-black">
                <SvgIcon icon="ri:send-plane-fill" />
              </span>
            </template>
          </NButton>
        </div>
      </div>
    </footer>
  </div>
</template>
